#include "t_spi_m.h"
#include "t_spi_m_interface.h"
#include <main.h>
#include "spi.h"
#define FLASH_CS_GPIO_PORT GPIOA
#define FLASH_CS_PIN GPIO_PIN_4

void Flash_CS_Low(void) {
    HAL_GPIO_WritePin(FLASH_CS_GPIO_PORT, FLASH_CS_PIN, GPIO_PIN_RESET);
//	j_spi_ss_set(spi,0);
}

void Flash_CS_High(void) {
    HAL_GPIO_WritePin(FLASH_CS_GPIO_PORT, FLASH_CS_PIN, GPIO_PIN_SET);
//	j_spi_ss_set(spi,1);
}

void th25d_read_jedec_id(t_spi_t *spi)
{
    uint8_t cmd[4] = {0x9f};
    uint8_t id[4] = {0};//2dummy

    Flash_CS_Low();

    // 先发送 RDID 指令
    t_spi_send_byte(spi, cmd, 1, 100);

   // 然后读取3字节 JEDEC ID
   t_spi_read_byte(spi, id, 3  , 100);
		//t_spi_SendRead_byte(spi,cmd,id,4,100);
		

    Flash_CS_High();

    printf("JEDEC ID: %02X %02X %02X\r\n", id[0], id[1], id[2]);

    if (id[0] == 0xCD && id[1] == 0x60 && id[2] == 0x13) {
        printf(">> Valid TH25D-40UB Chip <<\r\n");
    } else {
        printf(">> WARNING: Invalid ID! Expected: EB 60 13\r\n");
    }
}



/**
 * @brief 打印SPI Flash识别信息
 * @param spi SPI驱动实例
 */
/**
 * @brief 打印SPI Flash识别信息（适配新版API）
 * @param spi SPI实例指针
 */
void print_flash_identification(t_spi_t *spi)
{
    /* 文档定义的ID标准值 */
    #define TH25D_MANUFACTURER_ID   0xEB
    #define TH25D_MEMORY_TYPE       0x60
    #define TH25D_MEMORY_DENSITY    0x13
    #define TH25D_ELECTRONIC_ID     0x12
    #define TH25D_REMS_DEVICE_ID    0x12

    printf("\n======== SPI Flash Identification ========\n");

    /* 1. RDID命令 (9Fh) - 发送1字节命令，接收3字节数据 */
    uint8_t rdid_cmd = 0x9F;
    uint8_t rdid_data[3] = {0};
    
    if(HAL_SPI_TransmitReceive(&hspi1, &rdid_cmd, rdid_data, 1, 100) == SPI_OK) {
        printf("RDID (9Fh) Results:\n");
        printf("  Manufacturer ID: 0x%02X %s\n", 
               rdid_data[0], 
               rdid_data[0] == TH25D_MANUFACTURER_ID ? "(Valid)" : "(Invalid)");
        
        printf("  Memory Type:     0x%02X %s\n", 
               rdid_data[1], 
               rdid_data[1] == TH25D_MEMORY_TYPE ? "(Valid)" : "(Invalid)");
        
        printf("  Memory Density:  0x%02X %s\n", 
               rdid_data[2], 
               rdid_data[2] == TH25D_MEMORY_DENSITY ? "(Valid)" : "(Invalid)");
    } else {
        printf("[ERROR] RDID command failed!\n");
    }

    /* 2. RES命令 (ABh) - 发送1字节命令，接收1字节数据 */
    uint8_t res_cmd = 0xAB;
    uint8_t electronic_id = 0;
    
    if(HAL_SPI_TransmitReceive(&hspi1, &res_cmd, &electronic_id, 1, 100) == SPI_OK) {
        printf("\nRES (ABh) Results:\n");
        printf("  Electronic ID:   0x%02X %s\n",
               electronic_id,
               electronic_id == TH25D_ELECTRONIC_ID ? "(Valid)" : "(Invalid)");
    } else {
        printf("\n[WARNING] RES command not supported\n");
    }

    /* 3. REMS命令 (90h) - 需要特殊处理 */
    uint8_t rems_cmd[4] = {0x90, 0x00, 0x00, 0x00}; // 命令+3哑元
    uint8_t rems_data[2] = {0};
    
    /* 先发送4字节命令 */
    if(t_spi_send_byte(spi, rems_cmd, 4, 100) == SPI_OK) {
        /* 然后接收2字节数据 */
        if(t_spi_read_byte(spi, rems_data, 2, 100) == SPI_OK) {
            printf("\nREMS (90h) Results:\n");
            printf("  Manufacturer ID: 0x%02X %s\n",
                   rems_data[0],
                   rems_data[0] == TH25D_MANUFACTURER_ID ? "(Valid)" : "(Invalid)");
            
            printf("  Device ID:       0x%02X %s\n",
                   rems_data[1],
                   rems_data[1] == TH25D_REMS_DEVICE_ID ? "(Valid)" : "(Invalid)");
        }
    } else {
        printf("\n[WARNING] REMS command not supported\n");
    }

    /* 综合验证 */
    printf("\nValidation Summary:\n");
    if(rdid_data[0] == TH25D_MANUFACTURER_ID && 
       rdid_data[1] == TH25D_MEMORY_TYPE && 
       rdid_data[2] == TH25D_MEMORY_DENSITY) {
        printf("  >> Genuine TH25D-40UA Detected <<\n");
    } else {
        printf("  >> WARNING: Chip validation failed! <<\n");
        printf("     Expected IDs: MFID=0xEB, Type=0x60, Density=0x13\n");
    }
    
    printf("=========================================\n");
}
#define CMD_READ_DATA       0x03  // 读取数据
#define CMD_FAST_READ       0x0B  // 快速读取数据
#define CMD_PAGE_PROGRAM    0x02  // 页编程
#define CMD_SECTOR_ERASE    0x20  // 擦除扇区
#define CMD_BLOCK_ERASE     0xD8  // 擦除块
#define CMD_CHIP_ERASE      0xC7  // 擦除整个芯片
#define CMD_READ_STATUS     0x05  // 读取状态寄存器
#define CMD_WRITE_ENABLE    0x06  // 写使能
#define CMD_WRITE_DISABLE   0x04  // 写禁能
#define CMD_READ_ID         0x9F  // 读取设备 ID
#define CMD_READ_UID        0x4B  // 读取唯一 ID
#define CMD_POWER_DOWN      0xB9  // 进入掉电模式
#define CMD_RELEASE_POWER_DOWN 0xAB // 释放掉电模式
#define CMD_READ_JEDEC_ID   0x9F  // 读取 JEDEC ID
#define CMD_READ_SFDP       0x5A  // 读取 SFDP 寄存器
#define CMD_ERASE_SECURITY_REG 0x44 // 擦除安全寄存器
#define CMD_PROGRAM_SECURITY_REG 0x42 // 编程安全寄存器
#define CMD_READ_SECURITY_REG 0x48 // 读取安全寄存器

// SPI Flash 大小和地址定义
#define SECTOR_SIZE         4096
#define PAGE_SIZE           256
// CS 引脚配置



#include "t_spi_m.h"
void spi_transfer(uint8_t *tx_buffer, uint8_t *rx_buffer, uint16_t length){
	
    
    
	if(rx_buffer != NULL && tx_buffer == NULL){
//    HAL_SPI_Receive_DMA(&hspi_flash, rx_buffer, length);
     HAL_SPI_Receive(&hspi1, rx_buffer, length, HAL_MAX_DELAY);
		 //t_spi_read_byte(pspi, rx_buffer, length, 100);
//		SPI_ReceiveBytes(rx_buffer, length);
//		 j_spi_read(spi, rx_buffer,length);
  }else if(rx_buffer == NULL && tx_buffer != NULL){
//    HAL_SPI_Transmit_DMA(&hspi_flash, tx_buffer, length);
    HAL_SPI_Transmit(&hspi1, tx_buffer, length, HAL_MAX_DELAY);
		//t_spi_send_byte(pspi, rx_buffer, length, 100);
//    SPI_SendBytes(tx_buffer, length);
//		j_spi_write(spi, tx_buffer, length);
  }else if(rx_buffer != NULL && tx_buffer !=NULL){
//    HAL_SPI_TransmitReceive_DMA(&hspi_flash, tx_buffer, rx_buffer, length);
    // HAL_SPI_TransmitReceive(&hspi_flash, tx_buffer, rx_buffer, length,HAL_MAX_DELAY);
  }	
}

// 写使能
void spi_flash_write_enable() {
    uint8_t cmd = CMD_WRITE_ENABLE;
    Flash_CS_Low();
    spi_transfer(&cmd, NULL, 1);
    Flash_CS_High();
}

// 读取状态寄存器
uint8_t spi_flash_read_status() {
    uint8_t cmd = CMD_READ_STATUS;
    uint8_t status;
    Flash_CS_Low();
    spi_transfer(&cmd, NULL, 1);
    spi_transfer(NULL, &status, 1);
    Flash_CS_High();
    return status;
}

// 等待写入完成
void spi_flash_wait_for_write() {
    while (spi_flash_read_status() & 0x01) {
        // 等待写入完成
    }
}

// 读取数据
void spi_flash_read_data(uint32_t address, uint8_t *buffer, uint16_t length) {
    uint8_t cmd[4] = { CMD_READ_DATA, (address >> 16) & 0xFF, (address >> 8) & 0xFF, address & 0xFF };
    Flash_CS_Low();
    spi_transfer(cmd, NULL, 4);
    spi_transfer(NULL, buffer, length);
    Flash_CS_High();
}

// 写入数据（页编程）
void spi_flash_page_program(uint32_t address, const uint8_t *buffer, uint16_t length) {
    if (length > PAGE_SIZE) {
        length = PAGE_SIZE; // 页编程最大长度为 256 字节
    }
    uint8_t cmd[4] = { CMD_PAGE_PROGRAM, (address >> 16) & 0xFF, (address >> 8) & 0xFF, address & 0xFF };
    spi_flash_write_enable();
    Flash_CS_Low();
    spi_transfer(cmd, NULL, 4);
    spi_transfer((uint8_t *)buffer, NULL, length);
    Flash_CS_High();
    spi_flash_wait_for_write();
}

// 擦除扇区
void spi_flash_sector_erase(uint32_t address) {
    uint8_t cmd[4] = { CMD_SECTOR_ERASE, (address >> 16) & 0xFF, (address >> 8) & 0xFF, address & 0xFF };
    spi_flash_write_enable();
    Flash_CS_Low();
    spi_transfer(cmd, NULL, 4);
    Flash_CS_High();
    spi_flash_wait_for_write();
}

// 擦除整个芯片
void spi_flash_chip_erase() {
    uint8_t cmd = CMD_CHIP_ERASE;
    spi_flash_write_enable();
    Flash_CS_Low();
    spi_transfer(&cmd, NULL, 1);
    Flash_CS_High();
    spi_flash_wait_for_write();
}

// 读取设备 ID
void spi_flash_read_id(uint8_t *id_buf) {
    uint8_t cmd = CMD_READ_ID;
    Flash_CS_Low();
    spi_transfer(&cmd, NULL, 1);
    spi_transfer(NULL, id_buf, 3); // 通常设备 ID 是 3 字节
    Flash_CS_High();
}

// 块擦除函数实现
void spi_flash_block_erase(uint32_t address) {
    uint8_t cmd[4] = { CMD_BLOCK_ERASE, (address >> 16) & 0xFF, (address >> 8) & 0xFF, address & 0xFF };
		spi_flash_write_enable();
    Flash_CS_Low();
    spi_transfer(cmd, NULL, 4);
    Flash_CS_High();
    spi_flash_wait_for_write();
}
t_spi_t *pspi;
void init_soft_spi(void){
pspi = t_spi_create(
    "spi",
    T_SPI_NSS_NO,//推荐自己实现CS
    spi_gpio_cfgout,
    spi_gpio_cfgin,
    spi_gpio_t_delay,
    spi_gpio_write,
    spi_gpio_read,
    &gpio_spi
   );
}